package com.sofa.common.utils;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import lombok.extern.slf4j.Slf4j;

import java.lang.reflect.Field;
import java.util.*;


/**
 * 生成日志detail信息的工具类
 * 它会自动比较你传入的两个对象
 * 该工具类为ai辅助编写
 */
@Slf4j
public class OperationLogDetailUtils {

    private static final ObjectMapper mapper = new ObjectMapper();

    /**
     * 生成更新日志的detail信息(只支持业务对象的比较)
     * @param oldObj 原本的值
     * @param newObj 更新后的值
     * @return
     */
    public static String generateUpdateLog(Object oldObj, Object newObj) {
        if (oldObj == null || newObj == null) return "[]";
        if (!oldObj.getClass().equals(newObj.getClass())) {
            throw new IllegalArgumentException("对象类型不匹配");
        }

        List<Map<String, String>> diffs = new ArrayList<>();
        Class<?> clazz = oldObj.getClass();
        Field[] fields = clazz.getDeclaredFields();
        if (
            clazz.isPrimitive() ||  // 基本类型
            clazz.equals(String.class) || // String类型
            Number.class.isAssignableFrom(clazz) || // 数值类型
            clazz.isEnum()// 枚举类型
        ) {
            // 不支持对比纯值类型(像String, Integer等)
            return "[]";
        }

        //遍历属性
        for (Field field : fields) {
            field.setAccessible(true);
            try {
                Object oldVal = field.get(oldObj);
                Object newVal = field.get(newObj);

                // 如果新值是 null → 跳过
                if (newVal == null) continue;

                // 如果是空字符串，也跳过
                if (newVal instanceof String && ((String) newVal).trim().isEmpty()) continue;

                String oldStr = oldVal != null ? oldVal.toString() : "";
                String newStr = newVal.toString();

                if (!Objects.equals(oldStr, newStr)) {
                    //只有新旧值不相等时才记录
                    Map<String, String> diff = new LinkedHashMap<>();
                    diff.put("field", field.getName());
                    diff.put("old", oldStr);
                    diff.put("new", newStr);
                    diffs.add(diff);
                }

            } catch (IllegalAccessException e) {
                log.warn("字段对比失败：{}", field.getName(), e);
            }
        }

        try {
            return mapper.writeValueAsString(diffs);
        } catch (JsonProcessingException e) {
            log.warn("操作日志 JSON 序列化失败", e);
            return "[]";
        }
    }


    /**
     * 生成插入日志的detail信息
     * @param newObj 更新后的值
     * @return
     */
    public static String generateInsertLog(Object newObj) {
        if (newObj == null) {
            return "[]";
        }

        List<Map<String, String>> diffs = new ArrayList<>();
        Class<?> clazz = newObj.getClass();
        Field[] fields = clazz.getDeclaredFields();

        for (Field field : fields) {
            field.setAccessible(true);
            try {
                Object newVal = field.get(newObj);
                String newStr = newVal != null ? newVal.toString() : "";

                // 仅记录非空字段（可选：不记录空字段）
                if (!newStr.trim().isEmpty()) {
                    Map<String, String> diff = new LinkedHashMap<>();
                    diff.put("field", field.getName());
                    diff.put("old", "");
                    diff.put("new", newStr);
                    diffs.add(diff);
                }

            } catch (IllegalAccessException e) {
                log.warn("字段访问失败：{}", field.getName(), e);
            }
        }

        try {
            return mapper.writeValueAsString(diffs);
        } catch (JsonProcessingException e) {
            log.warn("插入日志 JSON 序列化失败", e);
            return "[]";
        }
    }


}
